#include"generalWidget.h"

GeneralWidget::GeneralWidget(QWidget* p):QWidget(p),ui(new Ui::GeneralWidget),filePath("")
{
    ui->setupUi(this);
    setInputMask();

    connect(ui->tableWidget_general_skill,SIGNAL(cellChanged(int,int)),this,SLOT(s_cellChanged(int,int)));
    connect(ui->tableWidget_general_skill,SIGNAL(cellDoubleClicked(int,int)),this,SLOT(s_cellDoubleClicked(int,int)));
}

GeneralWidget::~GeneralWidget()
{
    delete ui;
}

void GeneralWidget::setInputMask()
{
    QIntValidator* charValidator = new QIntValidator(-128,127,this);

    ui->lineEdit_general_starlevel->setValidator(charValidator);
    ui->lineEdit_general_attackRange->setValidator(charValidator);
    ui->lineEdit_general_defenseRange->setValidator(charValidator);
}

General GeneralWidget::getGeneralFromUI()
{
    General g;

    g.id = (qint32) ui->lineEdit_general_id->text().toInt();
    g.name = ui->lineEdit_general_name->text();
    g.description = ui->plainTextEdit_general_description->toPlainText();
    g.star_level = (qint8)ui->lineEdit_general_starlevel->text().toInt();
    g.country = (qint8)ui->comboBox_general_country->currentIndex();
    g.attack = (qint32)ui->lineEdit_general_baseAttack->text().toInt();
    g.attack_range = (qint8)ui->lineEdit_general_attackRange->text().toInt();
    g.defense = (qint32)ui->lineEdit_general_baseDefense->text().toInt();
    g.defense_range = (qint8)ui->lineEdit_general_defenseRange->text().toInt();
    g.attack_addon = (qint32)ui->lineEdit_general_attackAddon->text().toInt();
    g.defense_addon = (qint32)ui->lineEdit_general_defenseRange->text().toInt();

    int skill_cnt = 0;
    vector<int> skillList;
    while(ui->tableWidget_general_skill->item(skill_cnt,0))
    {
        skillList.push_back(ui->tableWidget_general_skill->item(skill_cnt,0)->text().toInt());
        skill_cnt++;
    }
    g.skillCount = skill_cnt;
    g.skill = new qint32[skill_cnt];
    for(int i=0;i<skill_cnt;i++)
        g.skill[i] = skillList[i];

    return g;
}

void GeneralWidget::displayGeneralToUI(General& g)
{
    clearUI();

    ui->lineEdit_general_id->setText(QString::number(g.id));
    ui->lineEdit_general_name->setText(g.name);
    ui->plainTextEdit_general_description->setPlainText(g.description);
    ui->lineEdit_general_starlevel->setText(QString::number(g.star_level));
    ui->comboBox_general_country->setCurrentIndex((int)g.country);
    ui->lineEdit_general_baseAttack->setText(QString::number(g.attack));
    ui->lineEdit_general_attackRange->setText(QString::number(g.attack_range));
    ui->lineEdit_general_baseDefense->setText(QString::number(g.defense));
    ui->lineEdit_general_defenseRange->setText(QString::number(g.defense_range));
    ui->lineEdit_general_attackAddon->setText(QString::number(g.attack_addon));
    ui->lineEdit_general_defenseAddon->setText(QString::number(g.defense_addon));

    for(qint32 i=0;i<g.skillCount;i++)
        ui->tableWidget_general_skill->setItem(i,0,new QTableWidgetItem(QString::number(g.skill[i])));
}

General GeneralWidget::readGeneralFromFile()
{
    General g;

    QFile f(filePath);
    if(f.exists())
    {
        f.open(QIODevice::ReadOnly);
        QDataStream in(&f);
        in>>g;
        displayGeneralToUI(g);
        f.close();
    }else
        WARNING_FILE_NOT_EXIST;

    return g;
}

bool GeneralWidget::saveGeneralToFile()
{
    if(ui->lineEdit_general_name->text().isEmpty()||filePath.isEmpty())
    {
        WARNING_NO_NAME;
        return false;
    }
    else
    {
        General g = getGeneralFromUI();
        QFile f(filePath);
        f.open(QIODevice::WriteOnly);
        QDataStream out(&f);
        out<<g;
        f.close();

        int idx1 = filePath.lastIndexOf("/");
        int idx2 = filePath.lastIndexOf(".");

        filePath.replace(idx1+1,idx2-idx1-1,ui->lineEdit_general_name->text());
        f.rename(filePath);
        return true;
    }
}

void GeneralWidget::clearUI()
{
    initialMap();

    ui->lineEdit_general_attackAddon->clear();
    ui->lineEdit_general_attackRange->clear();
    ui->lineEdit_general_baseAttack->clear();
    ui->lineEdit_general_baseDefense->clear();
    ui->lineEdit_general_defenseAddon->clear();
    ui->lineEdit_general_defenseRange->clear();
    ui->lineEdit_general_id->clear();
    ui->lineEdit_general_name->clear();
    ui->lineEdit_general_starlevel->clear();
    ui->plainTextEdit_general_description->clear();
    for(int i=0;i<ui->tableWidget_general_skill->rowCount();i++)
    {
        for(int j=0;j<ui->tableWidget_general_skill->columnCount();j++)
        {
            if(ui->tableWidget_general_skill->item(i,j))
                delete (ui->tableWidget_general_skill->takeItem(i,j));
        }
    }
}

void GeneralWidget::exportToBinary(QString workspacepath)
{
    //export general
    QFile f3(workspacepath+"/"+GENERAL_EXPORT_NAME);
    f3.open(QIODevice::WriteOnly);
    QDataStream out3(&f3);

    out3<<General::magic;
    out3<<General::version;

    QDir dir_generalType(workspacepath+"/"+GENERAL_STR);
    QStringList generalTypeList = dir_generalType.entryList(QDir::Dirs|QDir::NoDotAndDotDot);
    for(int i=0;i<generalTypeList.length();i++)
    {
        QDir dir_concreteGeneral(dir_generalType.absolutePath()+"/"+generalTypeList.at(i));
        QString mfilter = QString("*")+QString(GENERAL_FILE_SUFFIX);
        QStringList generalList = dir_concreteGeneral.entryList(QStringList(mfilter));
        for(int j=0;j<generalList.length();j++)
        {
            General g;
            QFile f31(dir_concreteGeneral.absolutePath()+"/"+generalList.at(j));
            f31.open(QIODevice::ReadOnly);
            QDataStream in(&f31);
            in>>g;
            out3<<g;
            f31.close();
        }
    }

    f3.close();
}

void GeneralWidget::exportToXML(QString workspacepath)
{
    //*****write XML*******//
    QFile file(workspacepath+"/output/general.xml");
    file.open(QIODevice::WriteOnly);
    QDomDocument doc;
    QDomText text;
    QDomProcessingInstruction instruction;
    instruction=doc.createProcessingInstruction("xml","version=\"1.0\" encoding=\"gb18030\"");
    doc.appendChild(instruction);
    QDomElement root=doc.createElement("root");
    doc.appendChild(root);

    QDir dir_type_root(workspacepath+"/"+GENERAL_STR);
    QStringList typeList = dir_type_root.entryList(QDir::Dirs|QDir::NoDotAndDotDot);
    int cnt_type = typeList.length();
    for(int i=0;i<cnt_type;i++)
    {
        QString tname;
        if(typeList.at(i)==QString::fromLocal8Bit(GENERAL_FIVE_STAR_STR))
        {
            tname = "fiveStar";
        }else if(typeList.at(i)==QString::fromLocal8Bit(GENERAL_FOUR_STAR_STR))
        {
            tname = "fourStar";
        }else if(typeList.at(i)==QString::fromLocal8Bit(GENERAL_THREE_STAR_STR))
        {
            tname = "threeStar";
        }else if(typeList.at(i)==QString::fromLocal8Bit(GENERAL_TWO_STAR_STR))
        {
            tname = "twoStar";
        }else if(typeList.at(i)==QString::fromLocal8Bit(GENERAL_ONE_STAR_STR))
        {
            tname = "oneStar";
        }
        else
        {
            tname = "other";
        }
        QDomElement typeElement=doc.createElement(tname);
        root.appendChild(typeElement);

        QDir dir_item(dir_type_root.absolutePath()+"/"+typeList.at(i));
        QStringList itemList = dir_item.entryList(QStringList()<<(QString("*")+GENERAL_FILE_SUFFIX));
        for(int j=0;j<itemList.length();j++)
        {
            QDomElement general=doc.createElement("general");
            typeElement.appendChild(general);

            General g;
            QFile mf(dir_item.absolutePath()+"/"+itemList.at(j));
            mf.open(QIODevice::ReadOnly);
            QDataStream in(&mf);
            in>>g;
            mf.close();

            QDomElement element;

            element=doc.createElement("id");
            text=doc.createTextNode(QString::number(g.id));
            element.appendChild(text);
            general.appendChild(element);

            element=doc.createElement("name");
            text=doc.createTextNode(g.name);
            element.appendChild(text);
            general.appendChild(element);

            element=doc.createElement("description");
            text=doc.createTextNode(g.description);
            element.appendChild(text);
            general.appendChild(element);

            element=doc.createElement("star_level");
            text=doc.createTextNode(QString::number(g.star_level));
            element.appendChild(text);
            general.appendChild(element);

            element=doc.createElement("country");
            text=doc.createTextNode(QString::number(g.country));
            element.appendChild(text);
            general.appendChild(element);

            element=doc.createElement("attack");
            text=doc.createTextNode(QString::number(g.attack));
            element.appendChild(text);
            general.appendChild(element);

            element=doc.createElement("attack_range");
            text=doc.createTextNode(QString::number(g.attack_range));
            element.appendChild(text);
            general.appendChild(element);

            element=doc.createElement("defense");
            text=doc.createTextNode(QString::number(g.defense));
            element.appendChild(text);
            general.appendChild(element);

            element=doc.createElement("defense_range");
            text=doc.createTextNode(QString::number(g.defense_range));
            element.appendChild(text);
            general.appendChild(element);

            element=doc.createElement("attack_addon");
            text=doc.createTextNode(QString::number(g.attack_addon));
            element.appendChild(text);
            general.appendChild(element);

            element=doc.createElement("defense_addon");
            text=doc.createTextNode(QString::number(g.defense_addon));
            element.appendChild(text);
            general.appendChild(element);

            int skillCnt = g.skillCount;
            for(int k=0;k<skillCnt;k++)
            {
                QDomElement element=doc.createElement("skillId");
                text=doc.createTextNode(QString::number(g.skill[k]));
                element.appendChild(text);
                general.appendChild(element);
            }
        }
    }

    QTextStream out(&file);
    doc.save(out,4);
    file.close();
}

bool GeneralWidget::importFromXML(QString workspacepath,QString xmlFile)
{
    QFile f(xmlFile);
    f.open(QIODevice::ReadOnly|QIODevice::Text);

    QDomDocument docment;

    if(!docment.setContent(&f,false))
    {
        return false;
    }

    QDir dir_root(workspacepath+"/"+GENERAL_STR);
    QDomElement root = docment.documentElement();

    QDomNodeList typeChildren = root.childNodes();
    if(typeChildren.length()!=5)
        return false;
    for(int i=0;i<typeChildren.length();i++)
    {
        QString typeName;
        if(typeChildren.at(i).toElement().tagName()==QString("fiveStar"))
        {
            typeName = QString::fromLocal8Bit(GENERAL_FIVE_STAR_STR);
        }else if(typeChildren.at(i).toElement().tagName()==QString("fourStar"))
        {
            typeName = QString::fromLocal8Bit(GENERAL_FOUR_STAR_STR);
        }else if(typeChildren.at(i).toElement().tagName()==QString("threeStar"))
        {
            typeName = QString::fromLocal8Bit(GENERAL_THREE_STAR_STR);
        }else if(typeChildren.at(i).toElement().tagName()==QString("twoStar"))
        {
            typeName = QString::fromLocal8Bit(GENERAL_TWO_STAR_STR);
        }else if(typeChildren.at(i).toElement().tagName()==QString("oneStar"))
        {
            typeName = QString::fromLocal8Bit(GENERAL_ONE_STAR_STR);
        }else
            continue;

        QDir typeDir(dir_root.absolutePath()+"/"+typeName);

        QDomNodeList elementList = typeChildren.at(i).toElement().childNodes();

        for(int j=0;j<elementList.length();j++)
        {
            QDomNodeList generalAtr = elementList.at(j).toElement().childNodes();

            General g;

            g.id = (qint32)generalAtr.at(0).toElement().text().toInt();
            g.name = generalAtr.at(1).toElement().text();
            g.description = generalAtr.at(2).toElement().text();
            g.star_level = (qint8)generalAtr.at(3).toElement().text().toInt();
            g.country = (qint8)generalAtr.at(4).toElement().text().toInt();
            g.attack = (qint32)generalAtr.at(5).toElement().text().toInt();
            g.attack_range = (qint8)generalAtr.at(6).toElement().text().toInt();
            g.defense = (qint32)generalAtr.at(7).toElement().text().toInt();
            g.defense_range = (qint8)generalAtr.at(8).toElement().text().toInt();
            g.attack_addon = (qint32)generalAtr.at(9).toElement().text().toInt();
            g.defense_addon = (qint32)generalAtr.at(10).toElement().text().toInt();

            QDomNodeList skillList = elementList.at(j).toElement().elementsByTagName(QString("skillId"));
            if(skillList.length()>0)
            {
                g.skillCount = skillList.length();
                g.skill = new qint32[skillList.length()];
                for(int k=0;k<skillList.length();k++)
                {
                    g.skill[i] = (qint32)skillList.at(k).toElement().text().toInt();
                }
            }

            QString generalName = g.name+QString(GENERAL_FILE_SUFFIX);

            QFile mf(typeDir.absolutePath()+"/"+generalName);
            mf.open(QIODevice::WriteOnly);
            QDataStream out(&mf);
            out<<g;
            mf.close();
        }
    }
    return true;
}

void GeneralWidget::initialMap()
{
    skillMap.clear();
    //initial skillMap
    QDir dir_skill(workPath+"/"+SKILL_STR);

    QString mfilter = QString("*")+QString(SKILL_FILE_SUFFIX);
    QStringList skillList = dir_skill.entryList(QStringList()<<mfilter);

    Skill s;

    for(int i=0;i<skillList.length();i++)
    {
        QFile f(dir_skill.absolutePath()+"/"+skillList.at(i));
        f.open(QIODevice::ReadOnly);
        QDataStream in(&f);
        in>>s;
        skillMap.insert((int)s.id,s.description);
        f.close();
    }

//    qDebug()<<skillMap.values();
}

//*************slot function*************//
void GeneralWidget::s_cellChanged(int row,int col)
{
//    qDebug()<<"cell("<<row<<","<<col<<") changed!";
    if(col==0)
    {
        int id = ui->tableWidget_general_skill->item(row,col)->text().toInt();
        ui->tableWidget_general_skill->setItem(row,col+1,new QTableWidgetItem(skillMap.value(id)));
    }
}

void GeneralWidget::s_cellDoubleClicked(int row,int col)
{
    if(col==1)
    {
//        if(!(ui->tableWidget_general_skill->item(row,col)->text().replace(" ","").isEmpty()))
//        {

//        }
        if(ui->tableWidget_general_skill->item(row,0))
            delete (ui->tableWidget_general_skill->item(row,0));
        if(ui->tableWidget_general_skill->item(row,1))
            delete (ui->tableWidget_general_skill->item(row,1));
    }
}
